Skip to content

fix(runtime): isolate detached worktrees and recover orphan groups#61

Merged
roodboi merged 6 commits into
mainfrom
codex/event-agent-runtime-repair
Jul 9, 2026
Merged

fix(runtime): isolate detached worktrees and recover orphan groups#61
roodboi merged 6 commits into
mainfrom
codex/event-agent-runtime-repair

Conversation

@roodboi

@roodboi roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor

Summary

  • refuse implicit base-instance targeting from detached linked worktrees while preserving explicit --branch and worktree.auto_branch=false opt-out behavior
  • recover persisted lifecycle process groups when the saved leader/pane PID is gone but live members remain in the exact saved PGID
  • surface leaderless lifecycle groups and their descendant groups through hack doctor and terminate them through normal hack down cleanup
  • persist the wrapped lifecycle command's actual PGID rather than the tmux pane shell's PGID
  • document checkout-local lifecycle ownership and sync all generated agent guidance

Problem evidence

An Event Agent detached linked worktree silently resolved to the base Compose project and produced mixed containers under event-agent: canonical-checkout containers and partially created linked-worktree replacements shared one Compose project. A prior lifecycle proxy group also survived after leader PID 41981 exited; members remained in PGID 41981, but doctor/down only recovered groups through a live saved pane PID and missed the orphan.

Root causes:

  1. resolveEffectiveBranch intentionally mapped detached linked worktrees to source: "none", which is indistinguishable from a primary checkout and selects the base instance.
  2. Lifecycle reconciliation ignored a persisted PGID when its original pane/leader PID disappeared. The existing no-session safety guard then prevented normal cleanup from reaching that group.

Behavior and compatibility

  • Attached worktrees, primary checkouts, explicit branches, collision-safe branch slugs, and worktree.auto_branch=false behavior are unchanged.
  • Detached linked worktrees now fail with E_USAGE unless the caller supplies --branch or explicitly opts into the base instance via config.
  • up, down, and restart --json preserve that failure as stable E_USAGE envelopes rather than E_UNEXPECTED.
  • Doctor can identify the narrow leaderless shape when the saved pane and group leader are absent but live processes still report the exact saved PGID, including descendant process groups rooted at its surviving members. Destructive hack down recovery additionally requires a matching live lifecycle mux session as ownership proof.
  • Tmux lifecycle startup records the wrapped command PID after setsid(), resolves its real PGID, and removes the transient PID handoff; sh -c execution remains unchanged.
  • A live group leader with a missing saved pane remains untrusted to preserve the existing PID-reuse safeguard.
  • sh -c, interactive stdin/TTY behavior, singleton adoption, and partial-listener rejection are unchanged and remain covered.
  • This does not add an early-exit readiness policy for lifecycle processes; that requires a separate explicit readiness/grace contract.

Verification

  • bun test ...focused runtime/worktree/doctor/status suites... — 100 passed, 0 failed after review hardening
  • direct bun test plus DB tests — 830 passed, 5 intentionally skipped, 0 failed after command-PGID hardening
  • bun run test:e2e:local — 8 passed, 3 Docker-tier skipped
  • bun run test:e2e:local:docker — 11 passed before the final PGID hardening; the final rerun hit a host Docker create timeout before fixture containers were created
  • final live lifecycle fixture proof before the blocked Compose phase — pane PID 20436, persisted wrapped command PID/PGID 20447, live Bun sleeper in PGID 20447, and tmux teardown removed group 20447
  • bun run typecheck — 2/2 packages passed
  • bun run lint — privacy check plus CLI/DB Ultracite checks passed
  • bun run build — compiled 515 modules
  • detached lifecycle JSON regression suite — 22 passed across branch resolution, run/exec, and up/down/restart --json
  • agent docs, Cursor, and Codex integration parity checks passed
  • bun run docs:cli-reference produced no drift
  • bun run build:release --skip-tests --no-clean --out=/tmp/hack-runtime-repair-release-smoke passed; the packaged binary reports hack v3.3.2 and contains the detached-worktree guard

Release Signal

  • Commit / squash title: fix(runtime): isolate detached worktrees and recover orphan groups
  • Release intent: fix
  • Should this PR trigger a release signal? yes
  • Equivalent release artifact: the Conventional Commit fix signal is consumed by the repository's semantic-release workflow to prepare the next patch version.

Semantic Surfaces

  • Affects hack run, hack exec, worktree branch resolution, runtime-state reconciliation, and lifecycle process cleanup: yes
  • Targeted tests: tests/branches-effective-branch.test.ts, tests/run-exec-branch-default.test.ts, tests/e2e/scenarios/worktree-branch-default.ts, tests/project-lifecycle-processes.test.ts, tests/project-lifecycle-hygiene.test.ts
  • Matching docs/instructions: docs/core.md, docs/architecture.md, src/agents/instruction-source.ts, and synchronized generated guidance

Risks / Follow-up

  • Existing mixed Compose ownership still requires one-time cleanup; this patch prevents recurrence but does not infer ownership for already-collided containers.
  • Leaderless cleanup requires a persisted lifecycle PGID. Missing/corrupt lifecycle state remains intentionally non-destructive.

@roodboi

roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 80a8dd28f7

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/lib/project-lifecycle-processes.ts Outdated
@roodboi

roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: f87e5cfbe5

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/lib/project-lifecycle-processes.ts Outdated
@roodboi

roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 57f2358df0

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/lib/project-lifecycle-processes.ts
@roodboi

roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 2f4a4bea94

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/commands/project.ts
@roodboi

roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 966b863d44

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/commands/project.ts
@roodboi

roodboi commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. Nice work!

Reviewed commit: f50f408430

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

@roodboi roodboi merged commit f1de71e into main Jul 9, 2026
4 checks passed
@roodboi roodboi deleted the codex/event-agent-runtime-repair branch July 9, 2026 20:41
roodboi pushed a commit that referenced this pull request Jul 9, 2026
## <small>3.3.3 (2026-07-09)</small>

* Merge pull request #61 from hack-dance/codex/event-agent-runtime-repair ([f1de71e](f1de71e)), closes [#61](#61)
* fix(cli): preserve usage code for lifecycle json ([f50f408](f50f408))
* fix(runtime): clean descendant lifecycle groups ([57f2358](57f2358))
* fix(runtime): isolate detached worktrees and recover orphan groups ([80a8dd2](80a8dd2))
* fix(runtime): persist wrapped command process group ([2f4a4be](2f4a4be))
* fix(runtime): retain session proof for lifecycle cleanup ([f87e5cf](f87e5cf))
* docs(cli): explain detached worktree targeting ([966b863](966b863))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant